import datetime

from flask import Flask, request, jsonify, render_template
from flask_cors import CORS

from database import get_conn
from utils import get_pass_week

app = Flask(__name__)
CORS(app)


@app.route('/hello')
def hello():
    return jsonify({"message": "Hello from Flask HTTP!"})


@app.route('/trace', methods=['POST'])
def trace():
    try:
        data = request.get_json(force=True)

        print("==> 收到上报数据:", data)

        time_str = data.get('time')
        name = data.get('name')
        action = data.get('action')
        is_eye_on = data.get('isEyeOn')
        if isinstance(is_eye_on, str):
            is_eye_on = is_eye_on.lower() == "true"
        print(time_str, name, action, is_eye_on)
        if not isinstance(time_str, str) or not name or not isinstance(action, int) or not isinstance(is_eye_on, bool):
            return jsonify({'code': 400, 'msg': '参数缺失或格式错误'}), 400

        # 尝试解析时间，确保格式正确
        try:
            datetime.datetime.strptime(time_str, "%Y-%m-%d %H:%M:%S")
        except ValueError:
            return jsonify({'code': 400, 'msg': '时间格式错误，需为 YYYY-MM-DD HH:MM:SS'}), 400

        conn = get_conn()
        try:
            with conn.cursor() as cursor:
                sql = '''INSERT INTO video_actions (time, name, action, isEyeOn) 
                         VALUES (%s, %s, %s, %s)'''
                cursor.execute(sql, (time_str, name, action, is_eye_on))
            conn.commit()
        except Exception as e:
            conn.rollback()
            print("数据库插入失败:", e)
            raise e
        finally:
            conn.close()

        return jsonify({'code': 200, 'msg': '保存成功'})

    except Exception as e:
        import traceback
        traceback.print_exc()
        return jsonify({'code': 500, 'msg': f'服务器错误：{str(e)}'}), 500


@app.route('/traces')
def get_traces():
    date_str = request.args.get('date')
    if not date_str:
        date_str = datetime.datetime.now().strftime('%Y-%m-%d')

    # 查询当天所有的上报记录
    sql = '''SELECT * FROM video_actions 
             WHERE time LIKE %s ORDER BY time ASC'''
    param = f"{date_str}%"

    try:
        conn = get_conn()
        with conn.cursor() as cursor:
            cursor.execute(sql, (param,))
            rows = cursor.fetchall()

            # ⚠️ 确保 time 是 datetime 类型（服务器返回可能是 str）
        for row in rows:
            if isinstance(row["time"], str):
                row["time"] = datetime.datetime.strptime(row["time"], "%Y-%m-%d %H:%M:%S")
    except Exception as e:
        return jsonify({'code': 500, 'msg': f'查询失败: {str(e)}'}), 500
    finally:
        conn.close()

    # timeline 构建
    timeline = []
    if rows:
        day_start = datetime.datetime.strptime(f"{date_str} 00:00:00", '%Y-%m-%d %H:%M:%S')
        last_time = None
        last_status = None

        for row in rows:
            curr_time = row['time']
            status = 'watching' if row['action'] == 1 and row['isEyeOn'] else \
                'no-eye' if row['action'] == 1 else 'paused'

            if last_time is not None:
                duration = (curr_time - last_time).total_seconds()
                if duration > 10:  # 忽略太短的
                    start_delta = (last_time - day_start).total_seconds()
                    left = start_delta / 86400 * 100
                    width = duration / 86400 * 100
                    timeline.append({
                        'start': last_time.strftime('%H:%M'),
                        'end': curr_time.strftime('%H:%M'),
                        'label': status_label(last_status),
                        'status': last_status,
                        'left': left,
                        'width': width
                    })
            last_time = curr_time
            last_status = status

        # 最后一段补到午夜
        day_end = day_start + datetime.timedelta(days=1)
        if last_time and last_time < day_end:
            duration = (day_end - last_time).total_seconds()
            start_delta = (last_time - day_start).total_seconds()
            left = start_delta / 86400 * 100
            width = duration / 86400 * 100
            timeline.append({
                'start': last_time.strftime('%H:%M'),
                'end': '24:00',
                'label': status_label(last_status),
                'status': last_status,
                'left': left,
                'width': width
            })

    # 视频汇总（每段视频播放开始结束）
    reports = []
    video_map = {}
    for row in rows:
        name = row['name']
        if name not in video_map:
            video_map[name] = {'name': name, 'start_time': row['time'], 'end_time': row['time']}
        else:
            video_map[name]['end_time'] = row['time']
    reports = list(video_map.values())

    return render_template(
        'trace_report.html',
        date=date_str,
        reports=reports,
        dates=list(reversed(get_pass_week())),
        timeline=timeline
    )


def status_label(status):
    return {
        'watching': '观看中',
        'no-eye': '未注视屏幕',
        'paused': '暂停中'
    }.get(status, '未知状态')


if __name__ == '__main__':
    app.run(host='0.0.0.0', port=8010, debug=False)
